package com.iceframework.core.support.security.util;

import java.util.Date;

import javax.crypto.spec.SecretKeySpec;
import javax.xml.bind.DatatypeConverter;

import org.apache.commons.codec.binary.Base64;
import org.springframework.stereotype.Component;

import com.iceframework.core.support.security.entity.IJWTInfo;

import io.jsonwebtoken.Claims;
import io.jsonwebtoken.JwtBuilder;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;

@Component
public class JwtUtils {
	public static String sercetKey = "iceframework";
	public static long keeptime = 1800000;

	public static String generToken(String id, String issuer, String subject) {
		long ttlMillis = keeptime;
		SignatureAlgorithm signatureAlgorithm = SignatureAlgorithm.HS256;
		long nowMillis = System.currentTimeMillis();
		Date now = new Date(nowMillis);
		byte[] apiKeySecretBytes = DatatypeConverter.parseBase64Binary(sercetKey);
		SecretKeySpec signingKey = new SecretKeySpec(apiKeySecretBytes, signatureAlgorithm.getJcaName());

		JwtBuilder builder = Jwts.builder().setId(id).setIssuedAt(now);
		if (subject != null) {
			builder.setSubject(subject);
		}
		if (issuer != null) {
			builder.setIssuer(issuer);
		}
		builder.signWith(signatureAlgorithm, signingKey);

		if (ttlMillis >= 0) {
			long expMillis = nowMillis + ttlMillis;
			Date exp = new Date(expMillis);
			builder.setExpiration(exp);
		}
		return builder.compact();
	}

	public static String updateToken(String token) {
		try {
			Claims claims = verifyToken(token);
			String id = claims.getId();
			String subject = claims.getSubject();
			String issuer = claims.getIssuer();
			return generToken(id, issuer, subject);
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return "0";
	}

	public String updateTokenBase64Code(String token) {
		try {
			token = new String(Base64.decodeBase64(token), "utf-8");
			Claims claims = verifyToken(token);
			String id = claims.getId();
			String subject = claims.getSubject();
			String issuer = claims.getIssuer();
			String newToken = generToken(id, issuer, subject);
			return Base64.encodeBase64String(newToken.getBytes());
		} catch (Exception ex) {
			ex.printStackTrace();
		}
		return "0";
	}

	public static Claims verifyToken(String token) {
		Claims claims = Jwts.parser().setSigningKey(DatatypeConverter.parseBase64Binary(sercetKey))
				.parseClaimsJws(token).getBody();
		return claims;
	}

	public static IJWTInfo getJWTInfoByToken(String token) {
		try {
			Claims claims = verifyToken(token);
			final String id = claims.getId();
			String subject = claims.getSubject();
			// claims.getIssuer();
			return new IJWTInfo() {
				@Override
				public String getUserId() {
					return id;
				}
				@Override
				public String getUserInfo() {
					return subject;
				}
			};
		} catch (Exception e) {
			// TODO: handle exception
		}
		return null;
	}

	public static void main(String[] args) {
		// 生成Token
		String token = JwtUtils.generToken("xiaoming", null, null);
		// eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiJ4aWFvbWluZyIsImlhdCI6MTU0MDAxODQ0NSwiZXhwIjoxNTQwMDIwMjQ1fQ.2ioR2dUE3HmZveW1XuU7zVFjv2PiPsIN7hsAXplDaiw
		// 解析token
		// String token =
		// "eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiJ4aWFvbWluZyIsImlhdCI6MTU0MDAxODQ0NSwiZXhwIjoxNTQwMDIwMjQ1fQ.2ioR2dUE3HmZveW1XuU7zVFjv2PiPsIN7hsAXplDaiw";
		// String updateToken = JwtUtils.updateToken(token);
		System.out.println(token);

	}

}